/**
 * Z-Fighting 修复助手
 * 提供工具函数来解决深度冲突问题
 */

import * as THREE from '../../lib/three/build/three.module.js';

export class ZFightingHelper {
    /**
     * 为材质应用多边形偏移
     * @param {THREE.Material} material - 要调整的材质
     * @param {number} factor - 偏移因子（默认 1）
     * @param {number} units - 偏移单位（默认 1）
     */
    static applyPolygonOffset(material, factor = 1, units = 1) {
        if (!material) return;
        
        material.polygonOffset = true;
        material.polygonOffsetFactor = factor;
        material.polygonOffsetUnits = units;
        material.needsUpdate = true;
        
        console.log(`✅ 应用多边形偏移: factor=${factor}, units=${units}`);
    }
    
    /**
     * 批量处理场景中的所有材质
     * @param {THREE.Scene} scene - 场景对象
     * @param {Object} options - 配置选项
     */
    static fixSceneZFighting(scene, options = {}) {
        const {
            factor = 1,
            units = 1,
            filter = null  // 可选的材质过滤函数
        } = options;
        
        let processedCount = 0;
        
        scene.traverse((object) => {
            if (object.isMesh && object.material) {
                const materials = Array.isArray(object.material) ? object.material : [object.material];
                
                materials.forEach(mat => {
                    // 如果提供了过滤函数，使用它来决定是否处理
                    if (filter && !filter(mat, object)) {
                        return;
                    }
                    
                    // 应用多边形偏移
                    mat.polygonOffset = true;
                    mat.polygonOffsetFactor = factor;
                    mat.polygonOffsetUnits = units;
                    mat.needsUpdate = true;
                    
                    processedCount++;
                });
            }
        });
        
        console.log(`✅ Z-Fighting 修复完成: 处理了 ${processedCount} 个材质`);
        return processedCount;
    }
    
    /**
     * 为特定节点应用多边形偏移
     * @param {TreeNode} node - 场景树节点
     * @param {number} factor - 偏移因子
     * @param {number} units - 偏移单位
     */
    static fixNodeZFighting(node, factor = 1, units = 1) {
        if (!node || !node.object3D) return 0;
        
        let processedCount = 0;
        
        node.object3D.traverse((object) => {
            if (object.isMesh && object.material) {
                const materials = Array.isArray(object.material) ? object.material : [object.material];
                
                materials.forEach(mat => {
                    mat.polygonOffset = true;
                    mat.polygonOffsetFactor = factor;
                    mat.polygonOffsetUnits = units;
                    mat.needsUpdate = true;
                    processedCount++;
                });
            }
        });
        
        console.log(`✅ 节点 "${node.name}" Z-Fighting 修复完成: 处理了 ${processedCount} 个材质`);
        return processedCount;
    }
    
    /**
     * 重置材质的多边形偏移
     * @param {THREE.Material} material - 材质
     */
    static resetPolygonOffset(material) {
        if (!material) return;
        
        material.polygonOffset = false;
        material.polygonOffsetFactor = 0;
        material.polygonOffsetUnits = 0;
        material.needsUpdate = true;
    }
    
    /**
     * 诊断场景中的 Z-Fighting 问题
     * @param {THREE.Scene} scene - 场景对象
     */
    static diagnoseZFighting(scene) {
        console.log('🔍 ===== Z-Fighting 诊断 =====');
        
        const issues = [];
        let totalMeshes = 0;
        let closeProximityPairs = 0;
        
        const meshes = [];
        scene.traverse((object) => {
            if (object.isMesh) {
                totalMeshes++;
                meshes.push(object);
            }
        });
        
        console.log(`📊 场景中共有 ${totalMeshes} 个 Mesh`);
        
        // 检查距离很近的面（简化版）
        // 实际生产环境中可能需要更复杂的空间检测
        for (let i = 0; i < meshes.length; i++) {
            for (let j = i + 1; j < meshes.length; j++) {
                const mesh1 = meshes[i];
                const mesh2 = meshes[j];
                
                const pos1 = new THREE.Vector3();
                const pos2 = new THREE.Vector3();
                
                mesh1.getWorldPosition(pos1);
                mesh2.getWorldPosition(pos2);
                
                const distance = pos1.distanceTo(pos2);
                
                // 如果两个 mesh 非常接近（小于 0.01 单位）
                if (distance < 0.01) {
                    closeProximityPairs++;
                    issues.push({
                        mesh1: mesh1.name || 'Unnamed',
                        mesh2: mesh2.name || 'Unnamed',
                        distance: distance.toFixed(4)
                    });
                }
            }
        }
        
        if (issues.length > 0) {
            console.log(`\n⚠️ 发现 ${issues.length} 对距离极近的 Mesh：`);
            issues.slice(0, 10).forEach((issue, index) => {
                console.log(`  ${index + 1}. ${issue.mesh1} ↔ ${issue.mesh2} (距离: ${issue.distance})`);
            });
            if (issues.length > 10) {
                console.log(`  ... 还有 ${issues.length - 10} 对`);
            }
            console.log('\n💡 建议：');
            console.log('  1. 使用 fixSceneZFighting() 批量修复');
            console.log('  2. 或调整模型中的面，增加距离');
        } else {
            console.log('\n✅ 未检测到明显的 Z-Fighting 风险');
        }
        
        console.log('🔍 ===== 诊断完成 =====');
        
        return issues;
    }
}

// 暴露到全局，方便在控制台使用
if (typeof window !== 'undefined') {
    window.ZFightingHelper = ZFightingHelper;
    
    // 快捷方法
    window.fixZFighting = function(factor = 1, units = 1) {
        if (!window.manager || !window.manager.getCurrentScene()) {
            console.error('❌ 场景未加载');
            return;
        }
        
        const scene = window.manager.getCurrentScene().scene;
        return ZFightingHelper.fixSceneZFighting(scene, { factor, units });
    };
    
    window.diagnoseZFighting = function() {
        if (!window.manager || !window.manager.getCurrentScene()) {
            console.error('❌ 场景未加载');
            return;
        }
        
        const scene = window.manager.getCurrentScene().scene;
        return ZFightingHelper.diagnoseZFighting(scene);
    };
    
    console.log('💡 Z-Fighting 工具已加载！');
    console.log('   使用 fixZFighting() 修复场景中的深度冲突');
    console.log('   使用 diagnoseZFighting() 诊断问题');
}

export default ZFightingHelper;




